package xyz.thoughtset.viewer.modules.datarel.service;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import lombok.SneakyThrows;
import org.springframework.beans.factory.InitializingBean;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.ObjectUtils;
import org.springframework.util.StringUtils;
import xyz.thoughtset.viewer.common.crud.core.service.BaseServiceImpl;
import xyz.thoughtset.viewer.modules.datarel.dao.DataRelDao;
import xyz.thoughtset.viewer.modules.datarel.entity.DataRel;

import java.io.Serializable;
import java.util.HashMap;
import java.util.HashSet;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.concurrent.atomic.LongAdder;
import java.util.stream.Collectors;

@Service
@Transactional
public class DataRelServiceImpl extends BaseServiceImpl<DataRelDao, DataRel> implements DataRelService {


    @Override
    public List<DataRel> saveRels(String pId, List<DataRel> dataRels) {
        if (ObjectUtils.isEmpty(dataRels)){ return dataRels; }
        QueryWrapper<DataRel> paramQuery = new QueryWrapper();
        paramQuery.lambda().eq(DataRel::getPid,pId).select(DataRel::getId);
        List<DataRel> oldParams = baseMapper.selectList(paramQuery);
        LongAdder longAdder = new LongAdder();
        HashSet relIds = new HashSet<>();
        for (DataRel ele : dataRels){
            if(!StringUtils.hasText(ele.getSource())){
                ele.setSource(pId);
            }
            ele.setPid(pId);
            longAdder.increment();
            ele.setOrderNum(longAdder.intValue());
            baseMapper.insertOrUpdate(ele);
            relIds.add(ele.getId());
        }
        if (!ObjectUtils.isEmpty(oldParams)){
            List<String> delIds = oldParams.stream()
                    .filter(e->!relIds.contains(e.getId()))
                    .map(DataRel::getId)
                    .collect(Collectors.toList());
            baseMapper.deleteByIds(delIds);
        }
        return dataRels;
    }

    @Override
    public List<DataRel> listByTopic(String topic) {
        QueryWrapper<DataRel> query = new QueryWrapper<>();
        query.eq("topic", topic);
        return list(query);
    }

    @Override
    public List<DataRel> listByTopicAndSId(String sourceId, String topic) {
        QueryWrapper<DataRel> query = new QueryWrapper<>();
        query.lambda()
                .eq(DataRel::getSource, sourceId)
                .eq(DataRel::getTopic, topic)
                .orderByAsc(DataRel::getOrderNum)
                .orderByDesc(DataRel::getUpdatedAt);
        return list(query);
    }

    @Override
    public HashMap<String, List<DataRel>> groupRelsByPid(String pid) {
        List<DataRel> dataRels = listByPId(pid);
        if (ObjectUtils.isEmpty(dataRels)) {
            return new HashMap<>();
        }
        HashMap<String, List<DataRel>> groupedRels = dataRels.stream()
                .collect(Collectors.groupingBy(DataRel::getTopic, HashMap::new, Collectors.toList()));
        return groupedRels;
    }

    @Override
    public List listByPId(String pid) {
        QueryWrapper<DataRel> queryWrapper = this.pidQueryWrapper(pid);
        queryWrapper.lambda()
                .orderByAsc(DataRel::getTopic)
                .orderByAsc(DataRel::getOrderNum)
                .orderByDesc(DataRel::getUpdatedAt);
        return list(queryWrapper);
    }

    @Override
    public int delRelsByPId(String pId) {
        return baseMapper.delete(pidQueryWrapper(pId));
    }

}
